package com.xique.door.service.impl;

import com.baomidou.mybatisplus.core.toolkit.ObjectUtils;
import com.xique.common.core.exception.BaseException;
import com.xique.common.core.utils.MathUtil;
import com.xique.common.core.utils.OrikaUtil;
import com.xique.common.core.utils.SecurityUtils;
import com.xique.common.core.utils.StringUtils;
import com.xique.door.bean.domain.*;
import com.xique.door.bean.search.build.BuildingDeviceListSearch;
import com.xique.door.bean.vo.user.UserExcelVo;
import com.xique.door.constant.UserConstant;
import com.xique.door.device.freeview.constant.CommandStatus;
import com.xique.door.mapper.*;
import com.xique.door.service.*;
import lombok.extern.log4j.Log4j2;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Propagation;
import org.springframework.transaction.annotation.Transactional;

import java.util.ArrayList;
import java.util.Date;
import java.util.List;

@Service
@Log4j2
public class UserExceServiceImpl implements IUserExceService {

    @Autowired
    private IBuildAreaService buildAreaService;

    @Autowired
    private BuildAreaMapperV1 buildAreaMapperV1;

    @Autowired
    private IBuildBuildingService buildBuildingService;

    @Autowired
    private BuildBuildingMapperV1 buildBuildingMapperV1;

    @Autowired
    private IBuildingDeviceService buildingDeviceService;

    @Autowired
    private IBuildHouseService buildHouseService;

    @Autowired
    private BuildHouseMapperV1 buildHouseMapperV1;

    @Autowired
    private IUserService userService;

    @Autowired
    private UserMapperV1 userMapperV1;

    @Autowired
    private BuildHouseUserMapperV1 buildHouseUserMapperV1;

    @Autowired
    private IBuildHouseUserService buildHouseUserService;

    @Autowired
    private IAccessDeviceService accessDeviceService;

    @Autowired
    private IUserDeviceService userDeviceService;

    @Autowired
    private IBaseUserService baseUserService;

    @Autowired
    private IParkInfoService parkInfoService;

    @Autowired
    private IUserAndBaseUserBizService userAndBaseUserBizService;


    @Override
    @Transactional(rollbackFor = Exception.class, propagation = Propagation.REQUIRED)
    public String initialization(Long parkId, List<UserExcelVo> userExcelVos) {

        // 初始化成功、失败消息及消息编号
        int successNum = 0;
        int failureNum = 0;
        ParkInfo parkInfo = parkInfoService.selectParkInfoById(parkId);
        StringBuilder successMsg = new StringBuilder();
        StringBuilder failureMsg = new StringBuilder();
        User userSearch = new User();
        userSearch.setParkId(parkId);

        for (UserExcelVo vo : userExcelVos) {
            Long areaId = null;
            String code = null;

            if (vo.getAreaName() != null
                    && !"".equals(vo.getAreaName())
                    && StringUtils.isNotEmpty(vo.getNumber())) {
                /** 区域 */
                BuildAreaV1 buildAreaV1 = new BuildAreaV1();

                buildAreaV1.setAreaName(vo.getAreaName());
                buildAreaV1.setParkId(parkId);
                BuildAreaV1 buildAreaV2 = buildAreaService.selectAreaV1(buildAreaV1);

                if (buildAreaV2 == null) {
                    buildAreaV1.setCreateTime(new Date());
                    buildAreaV1.setDelFlag("0");
                    buildAreaV1.setRemark("初始化导入数据");
                    buildAreaV1.setStatus("normal");
                    code = buildAreaService.getCode(parkId);
                    if (code.length() == 1) {
                        code = "0" + code;
                    }
                    buildAreaV1.setCode(code);
                    buildAreaV1.setCreateBy(SecurityUtils.getUserId());
                    buildAreaV1.setUpdateBy(SecurityUtils.getUserId());
                    buildAreaV1.setUpdateTime(new Date());
                    buildAreaMapperV1.insert(buildAreaV1);
                    areaId = buildAreaV1.getId();
                } else {
                    areaId = buildAreaV2.getId();
                    code = buildAreaV2.getCode();
                }
            }
            Long buildingid = null;
            String buildingName = null;
            String buildingCode = null;
            if (vo.getBuildingName() != null && !"".equals(vo.getBuildingName()) && areaId != null) {
                /** 楼栋 */
                BuildBuildingV1 buildBuildingV1 = new BuildBuildingV1();
                String str = vo.getBuildingName();
                String buildingNames = null;
                String building = str.substring(0, str.indexOf("幢"));
                String unit = str.substring(str.indexOf("幢") + 1, str.indexOf("单元"));
                if (building.length() == 2 && building.indexOf("0") == 0) {
                    buildingNames = str.substring(1, str.indexOf("幢")) + "幢";
                } else {
                    buildingNames = str.substring(0, str.indexOf("幢")) + "幢";
                }
                if (unit.length() == 2 && unit.indexOf("0") == 0) {
                    buildingNames = buildingNames + unit.substring(1) + "单元";
                } else {
                    buildingNames = buildingNames + unit + "单元";
                }
                buildBuildingV1.setBuildingName(buildingNames);
                buildBuildingV1.setAreaId(areaId);
                buildBuildingV1.setParkId(parkId);
                BuildBuildingV1 buildBuildingV2 =
                        buildBuildingService.selectBuildBuildingV1(buildBuildingV1);
                if (buildBuildingV2 == null) {
                    buildBuildingV1.setCreateTime(new Date());
                    buildBuildingV1.setDelFlag("0");
                    buildBuildingV1.setRemark("初始化导入数据");
                    buildBuildingV1.setStatus("normal");
                    buildBuildingV1.setCreateBy(SecurityUtils.getUserId());

                    //String unit = str.substring(str.indexOf("幢") + 1, str.indexOf("单元"));
                    if (building.length() == 1) {
                        building = "0" + building;
                    }
                    if (unit.length() == 1) {
                        unit = "0" + unit;
                    }
                    buildBuildingV1.setCode(code + building + unit);
                    buildBuildingV1.setUnitCode(unit);
                    buildBuildingV1.setBuildingCode(building);
                    buildBuildingV1.setUpdateBy(SecurityUtils.getUserId());
                    buildBuildingV1.setUpdateTime(new Date());
                    buildBuildingMapperV1.insert(buildBuildingV1);
                    buildingid = buildBuildingV1.getId();
                    buildingName = buildBuildingV1.getBuildingName();
                    buildingCode = buildBuildingV1.getCode();
                } else {
                    buildingid = buildBuildingV2.getId();
                    buildingName = buildBuildingV2.getBuildingName();
                    buildingCode = buildBuildingV2.getCode();
                }

                //墙外机的情况
                AccessDevice accessDevice = new AccessDevice();
                accessDevice.setAccessType("park");
                accessDevice.setParkId(parkId);
                List<AccessDevice> accessDevices = accessDeviceService.selectAccessDeviceList(accessDevice);
                if (accessDevices != null && accessDevices.size() > 0) {

                    for (AccessDevice v : accessDevices) {
                        BuildingDevice buildingDevices = new BuildingDevice();
                        buildingDevices.setBuildingId(buildingid);
                        buildingDevices.setDeviceId(v.getId());
                        List<BuildingDevice> daoList =
                                buildingDeviceService.selectBuildingDeviceList(buildingDevices);
                        if (daoList.size() == 0) {
                            BuildingDevice buildingDevice = new BuildingDevice();
                            buildingDevice.setBuildingId(buildingid);
                            buildingDevice.setParkId(parkId);
                            buildingDevice.setCreateBy(SecurityUtils.getUserId().toString());
                            buildingDevice.setUpdateBy(SecurityUtils.getUserId().toString());
                            buildingDevice.setDeviceId(v.getId());
                            buildingDeviceService.insertBuildingDevice(buildingDevice);
                        }

                    }
                }

            }
            Long houseId = null;
            String houseName = null;
            if (vo.getHouseCode() != null && !"".equals(vo.getHouseCode()) && buildingid != null) {
                /** 房号 */
                BuildHouseV1 buildHouseV1 = new BuildHouseV1();
                buildHouseV1.setParkId(parkId);
                buildHouseV1.setBuildingId(buildingid);
                buildHouseV1.setHouseCode(vo.getHouseCode());
                BuildHouseV1 buildHouseV2 = buildHouseService.selectBuildHouseV1(buildHouseV1);
                if (buildHouseV2 == null
                        && buildHouseV1.getHouseCode() != null
                        && !"".equals(buildHouseV1.getHouseCode())) {
                    buildHouseV1.setBuildingName(buildingName);
                    String str = buildHouseV1.getHouseCode();
                    String floor = str.substring(0, 2);
                    buildHouseV1.setFloor(Long.valueOf(floor));
                    buildHouseV1.setCode(buildingCode + buildHouseV1.getHouseCode());
                    buildHouseV1.setHouseName(buildHouseV1.getHouseCode() + "室");
                    buildHouseV1.setCreateTime(new Date());
                    buildHouseV1.setCreateBy(SecurityUtils.getUserId());
                    buildHouseV1.setRemark("初始化导入数据");
                    buildHouseV1.setUpdateBy(SecurityUtils.getUserId());
                    buildHouseV1.setUpdateTime(new Date());
                    buildHouseV1.setBuildingId(buildingid);
                    if (parkInfo.getMaxInNumber() == null) {
                        buildHouseV1.setMaxInNumber(10);
                    } else {
                        buildHouseV1.setMaxInNumber(parkInfo.getMaxInNumber());
                    }
                    buildHouseMapperV1.insert(buildHouseV1);
                    houseId = buildHouseV1.getId();
                    houseName = buildHouseV1.getHouseName();
                } else {
                    houseId = buildHouseV2.getId();
                    houseName = buildHouseV2.getHouseName();
                }
            }
            BuildHouseUserV1 buildHouseUserV2s = new BuildHouseUserV1();

            BuildHouseV1 houseV1 = buildHouseService.getById(houseId);
            if (!StringUtils.isNull(houseV1) && !StringUtils.isNull(houseV1.getMaxInNumber())) {
                int count = buildHouseUserService.checkHouseUserCount(houseId);
                if (count >= houseV1.getMaxInNumber()) {
                    failureNum++;
                    failureMsg.append(
                            "<br/>" + failureNum + "、" + "第" + vo.getNumber() + "已超出该房屋最大可入住数量!");
                    continue;
                }
            }

            Long userId = null;
            if (vo.getUserName() != null
                    && vo.getPhone() != null
                    && vo.getIdentityType() != null
                    && !"".equals(vo.getUserName())
                    && !"".equals(vo.getPhone())
                    && !"".equals(vo.getIdentityType())
                    && houseId != null) {

                UserV1 userV1 = new UserV1();
                userV1.setPhone(vo.getPhone());
                userV1.setParkId(parkId);
                UserV1 userV2 = userService.selectUserV1(userV1);
                String gender = null;
                if (vo.getSex().equals("男")) {
                    gender = UserConstant.Gender.MAN;
                } else if (vo.getSex().equals("女")) {
                    gender = UserConstant.Gender.WOMEN;
                } else {
                    gender = UserConstant.Gender.UNKNOWN;
                }
                if (userV2 == null) {
                    userV1.setPersonType(0);
                    userV1.setGender(gender);
                    userV1.setUserName(vo.getUserName());
                    userV1.setRemark("初始化导入数据");
                    userV1.setCreateUser(SecurityUtils.getUserId());
                    userV1.setUpdateUser(SecurityUtils.getUserId());
                    String customId = System.currentTimeMillis() + MathUtil.getRandom(19);
                    userV1.setCustomId(customId);
                    userV1.setIdentityType(vo.getIdentityType());
                    //C端用户处理
                    BaseUser baseUser = OrikaUtil.convert(userV1, BaseUser.class);
                    baseUser.setCellphone(userV1.getPhone());
                    BaseUser addBaseUser = userAndBaseUserBizService.userAddOrGetBaseUser(baseUser, "[门禁系统导入人员]");
                    userV1.setBaseUserId(addBaseUser.getId());
                    userMapperV1.insert(userV1);

                    if (vo.getIdentityType() != null) {
                        if (vo.getIdentityType().equals("0")) {
                            BuildHouseUserV1 buildHouseUserV1s = new BuildHouseUserV1();
                            buildHouseUserV1s.setHouseId(houseId);
                            buildHouseUserV1s.setBuildingId(buildingid);
                            buildHouseUserV1s.setIdentityType("0");
                            buildHouseUserV2s = buildHouseUserService.selectBuildHouseUserV1(buildHouseUserV1s);
                            if (buildHouseUserV2s != null) {
                                failureNum++;
                                failureMsg.append(
                                        "<br/>" + failureNum + "、" + "第" + vo.getNumber() + "个用户导入的房号已存在业主!");
                                continue;
                            }
                        }
                        if (!vo.getIdentityType().equals("0")
                                && !vo.getIdentityType().equals("1")
                                && !vo.getIdentityType().equals("2")) {
                            failureNum++;
                            failureMsg.append("<br/>" + failureNum + "、" + "第" + vo.getNumber() + "个身份类型错误!");
                            break;
                        }
                    }

                    userId = userV1.getId();
                    BuildingDeviceListSearch buildingDeviceListSearch = new BuildingDeviceListSearch();
                    buildingDeviceListSearch.setBuildingId(buildingid);
                    List<BuildingDevice> daoList =
                            buildingDeviceService.selectBuildingDeviceListWithDevice(buildingDeviceListSearch);
                    if (daoList.size() > 0) {
                        List<UserDevice> userDeviceList = new ArrayList<>();
                        for (BuildingDevice dao : daoList) {
                            AccessDevice vi = accessDeviceService.selectAccessDeviceById(dao.getDeviceId());
                            if (vi != null) {
                                UserDevice userDevice1 = new UserDevice();
                                userDevice1.setUserId(userId);
                                userDevice1.setParkId(parkId);
                                userDevice1.setDeviceId(vi.getId());
                                userDevice1.setDevSn(vi.getDevSn());
                                userDevice1.setModel(vi.getModel());
                                userDevice1.setRemark("初始化导入数据");
                                userDevice1.setCustomId(userV1.getCustomId());
                                userDevice1.setCreateUser(SecurityUtils.getUserId());
                                userDevice1.setUpdateUser(SecurityUtils.getUserId());
                                userDevice1.setStatus(CommandStatus.NOFACE);
                                userDeviceList.add(userDevice1);
                            }
                        }
                        userDeviceService.batchInsertUserDevice(userDeviceList);
                    }
                } else {
                    //BC端用户处理
                    userV2.setUserName(vo.getUserName());
                    userV2.setIdentityType(vo.getIdentityType());
                    userV2.setGender(gender);
                    userV2.setRemark("初始化导入数据");
                    User user = OrikaUtil.convert(userV2, User.class);
                    userAndBaseUserBizService.updateUserNoCheck(user,"[门禁系统导入人员]",userV2.getBaseUserId(),false);

                    userId = userV2.getId();
                    BuildingDeviceListSearch buildingDeviceListSearch = new BuildingDeviceListSearch();
                    buildingDeviceListSearch.setBuildingId(buildingid);
                    List<BuildingDevice> daoList =
                            buildingDeviceService.selectBuildingDeviceListWithDevice(buildingDeviceListSearch);
                    if (daoList.size() > 0) {
                        List<UserDevice> userDeviceList = new ArrayList<>();
                        for (BuildingDevice dao : daoList) {
                            UserDevice userDevice = new UserDevice();
                            userDevice.setUserId(userId);
                            userDevice.setDeviceId(dao.getDeviceId());
                            List<UserDevice> userDeviceList1 = userDeviceService.selectUserDeviceList(userDevice);
                            if (userDeviceList1.size() == 0) {
                                AccessDevice vi = accessDeviceService.selectAccessDeviceById(dao.getDeviceId());
                                if (ObjectUtils.isNotNull(vi)) {
                                    UserDevice userDevice1 = new UserDevice();
                                    userDevice1.setUserId(userId);
                                    userDevice1.setParkId(parkId);
                                    userDevice1.setDeviceId(vi.getId());
                                    userDevice1.setDevSn(vi.getDevSn());
                                    userDevice1.setModel(vi.getModel());
                                    userDevice1.setRemark("初始化导入数据");
                                    userDevice1.setCustomId(userV1.getCustomId());
                                    userDevice1.setCreateUser(SecurityUtils.getUserId());
                                    userDevice1.setUpdateUser(SecurityUtils.getUserId());
                                    userDevice1.setStatus(CommandStatus.NOFACE);
                                    userDeviceList.add(userDevice1);
                                }

                            }
                        }
                        userDeviceService.batchInsertUserDevice(userDeviceList);
                    }
                }
                BuildHouseUserV1 buildHouseUserV1 = new BuildHouseUserV1();
                buildHouseUserV1.setHouseId(houseId);
                buildHouseUserV1.setUserId(userId);
                buildHouseUserV1.setBuildingId(buildingid);
                BuildHouseUserV1 buildHouseUserV2 =
                        buildHouseUserService.selectBuildHouseUserV1(buildHouseUserV1);
                if (buildHouseUserV2 == null) {
                    buildHouseUserV1.setHouseName(houseName);
                    buildHouseUserV1.setUserName(vo.getUserName());
                    buildHouseUserV1.setBuildingId(buildingid);
                    buildHouseUserV1.setBuildingName(buildingName);
                    buildHouseUserV1.setIdentityType(vo.getIdentityType());
                    buildHouseUserMapperV1.insert(buildHouseUserV1);
                }
                successNum++;
                successMsg.append(
                        "<br/>" + successNum + "、用户【" + vo.getUserName() + "-" + vo.getPhone() + "】 导入成功");
            } else {
                if (StringUtils.isEmpty(vo.getNumber()) || "".equals(vo.getNumber())) {
                    failureNum++;
                    failureMsg.append("<br/>" + failureNum + "、" + "有一个序号为空，请检查序号");
                    break;
                }
                if (StringUtils.isEmpty(vo.getUserName()) || "".equals(vo.getUserName())) {
                    failureNum++;
                    failureMsg.append("<br/>" + failureNum + "、" + "第" + vo.getNumber() + "个用户姓名为空!");
                    break;
                }
                if (StringUtils.isEmpty(vo.getAreaName()) || "".equals(vo.getAreaName())) {
                    failureNum++;
                    failureMsg.append("<br/>" + failureNum + "、" + "第" + vo.getNumber() + "个区域为空!");
                    break;
                }
                if (StringUtils.isEmpty(vo.getHouseCode()) || "".equals(vo.getHouseCode())) {
                    failureNum++;
                    failureMsg.append("<br/>" + failureNum + "、" + "第" + vo.getNumber() + "个房号为空!");
                    break;
                }
                if (StringUtils.isEmpty(vo.getBuildingName()) || "".equals(vo.getBuildingName())) {
                    failureNum++;
                    failureMsg.append("<br/>" + failureNum + "、" + "第" + vo.getNumber() + "个楼栋单元为空!");
                    break;
                }
                if (StringUtils.isEmpty(vo.getPhone()) || "".equals(vo.getPhone())) {
                    failureNum++;
                    failureMsg.append("<br/>" + failureNum + "、" + "第" + vo.getNumber() + "个用户手机号为空!");
                    break;
                }
                if (StringUtils.isEmpty(vo.getIdentityType()) || !"".equals(vo.getIdentityType())) {
                    failureNum++;
                    failureMsg.append("<br/>" + failureNum + "、" + "第" + vo.getNumber() + "个身份类型号为空!");
                    break;
                }
            }
        }
        if (failureNum > 0) {
            failureMsg.insert(0, "很抱歉，部分数据校验失败！共 " + failureNum + " 条数据校验失败，错误如下：");
            log.error(failureMsg.toString());
            throw new BaseException(failureMsg.toString());
        } else {
            successMsg.insert(0, "恭喜您，数据已全部导入成功！共 " + successNum + " 条，数据如下：");
        }
        log.info(successMsg.toString());
        return successMsg.toString();
    }
}
